package uk.co.davedexter.flickruploader;

import java.io.BufferedReader;
import java.io.File;
import java.io.IOException;
import java.io.InputStreamReader;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Iterator;

import org.apache.sanselan.ImageReadException;
import org.apache.sanselan.Sanselan;
import org.apache.sanselan.common.IImageMetadata;
import org.apache.sanselan.formats.jpeg.JpegImageMetadata;
import org.apache.sanselan.formats.tiff.TiffField;
import org.apache.sanselan.formats.tiff.constants.TagInfo;
import org.apache.sanselan.formats.tiff.constants.TiffConstants;

public class DateTakenTest {
	
	private HashMap map;
	private ArrayList<File> noDate;
	
	DateTakenTest() {
		map = new HashMap();
		noDate = new ArrayList<File>();
	}
	
	private void processImageDirectory(File dir) {
		readPhotoFiles(dir);
		System.out.println("\n\n" + noDate);
	}
	
	private void readPhotoFiles(File dir) {
		if (dir.isDirectory()) {
			String[] children = dir.list();
			for (int i = 0; i < children.length; i++) {
				readPhotoFiles(new File(dir, children[i]));
			}
		} else {
			String filename = dir.getName();
			String ext = (filename.lastIndexOf(".") == -1) ? "" : filename.substring(filename.lastIndexOf(".") + 1,
					filename.length());
			if (ext.toLowerCase().equals("jpg") | ext.toLowerCase().equals("jpeg")) {
				System.out.println(dir);
				boolean dateFound = false;
				
				IImageMetadata metadata;
				try {
					metadata = Sanselan.getMetadata(dir);
			        
					if (metadata instanceof JpegImageMetadata)
			        {
			            JpegImageMetadata jpegMetadata = (JpegImageMetadata) metadata;
			            String createDate = jpegMetadata.findEXIFValue(TiffConstants.TIFF_TAG_DATE_TIME).getStringValue();
			            System.out.println("\t" + createDate);
			            dateFound = true;
			            map.put(dir, createDate);
			        } else {
			        	String result = getDateWithImageMagick(dir);
			        	System.out.println("\t" + result);
			        }
				} catch (ImageReadException e) {
					e.printStackTrace();
				} catch (IOException e) {
					e.printStackTrace();
				}

				
//				try {
//					Metadata metadata = JpegMetadataReader.readMetadata(dir);
//					
//					// iterate through metadata directories 
//					Iterator directories = metadata.getDirectoryIterator(); 
//					while (directories.hasNext()) { 
//						Directory directory = (Directory)directories.next(); // iterate through tags and print to System.out 
//						Iterator tags = directory.getTagIterator(); 
//						while (tags.hasNext()) { 
//							Tag tag = (Tag)tags.next(); // use Tag.toString()
//							if (tag.getTagName().equals("Date/Time")) {
//								System.out.println("\t" + tag.getDescription());
//								dateFound = true;
//								map.put(dir, tag.getDescription());
//							}
//						}
//					}
//				} catch (JpegProcessingException e) {
//					e.printStackTrace();
//				} catch (MetadataException e) {
//					e.printStackTrace();
//				}
				
				if (!dateFound) {
					System.out.println("\tLooking for a Raw image (CR2).");
					File rawFile = new File(dir.toString().replace("/JPEG/", "/").replace(".cr2.jpg", ".CR2"));
					if (rawFile.exists()) {
						System.out.println("Found" + rawFile);
//						try {
//							Metadata metadata = JpegMetadataReader.readMetadata(rawFile);
//							
//							// iterate through metadata directories 
//							Iterator directories = metadata.getDirectoryIterator(); 
//							while (directories.hasNext()) { 
//								Directory directory = (Directory)directories.next(); // iterate through tags and print to System.out 
//								Iterator tags = directory.getTagIterator(); 
//								while (tags.hasNext()) { 
//									Tag tag = (Tag)tags.next(); // use Tag.toString()
//									if (tag.getTagName().equals("Date/Time")) {
//										System.out.println("\t" + tag.getDescription());
//										dateFound = true;
//										map.put(dir, tag.getDescription());
//									}
//								}
//							}
//						} catch (JpegProcessingException e) {
//							e.printStackTrace();
//						} catch (MetadataException e) {
//							e.printStackTrace();
//						}
					}
				}
				
				if (!dateFound) {
					System.out.println("\tLooking for a Raw image (cr2).");
					File rawFile = new File(dir.toString().replace("/JPEG/", "/").replace(".cr2.jpg", ".cr2")); 
					if (rawFile.exists()) {
						System.out.println("Found");
//						try {
//							Metadata metadata = JpegMetadataReader.readMetadata(rawFile);
//							
//							// iterate through metadata directories 
//							Iterator directories = metadata.getDirectoryIterator(); 
//							while (directories.hasNext()) { 
//								Directory directory = (Directory)directories.next(); // iterate through tags and print to System.out 
//								Iterator tags = directory.getTagIterator(); 
//								while (tags.hasNext()) { 
//									Tag tag = (Tag)tags.next(); // use Tag.toString()
//									if (tag.getTagName().equals("Date/Time")) {
//										System.out.println("\t" + tag.getDescription());
//										dateFound = true;
//										map.put(dir, tag.getDescription());
//									}
//								}
//							}
//						} catch (JpegProcessingException e) {
//							e.printStackTrace();
//						} catch (MetadataException e) {
//							e.printStackTrace();
//						}
					}
				}
				
				if (!dateFound) {
					System.out.println("\tCould not find date!");
					noDate.add(dir);
				}
				
//				String[] fileParts = dir.toString().replace(topLevelPhotoDir.toString() + File.separator, "")
//						.split(File.separator);
//				String tags = "";
//				for (int i = 0; i < fileParts.length - 1; i++) {
//					tags += fileParts[i].replace(" - ", ": ").replace("-", ".") + ";";
//				}
//				tags = tags.substring(0, tags.length() - 1);
				// System.out.println(dir);
				// System.out.println(tags);
//				processImage(dir, tags);

			}
		}
	}
	
	private String getDateWithImageMagick(File file) {
		String s = null;
		ArrayList<String> lines = new ArrayList<String>();
		ArrayList<String> errorLines = new ArrayList<String>();

        try {
//            Process p = Runtime.getRuntime().exec("identify -verbose " + file + "|grep DateTime:");
        	Process p = Runtime.getRuntime().exec("identify -verbose " + file);
            
            BufferedReader stdInput = new BufferedReader(new 
                 InputStreamReader(p.getInputStream()));

            BufferedReader stdError = new BufferedReader(new 
                 InputStreamReader(p.getErrorStream()));

            // read the output from the command
            while ((s = stdInput.readLine()) != null) {
//            	System.out.println(s);
                lines.add(s);
            }
            
            // read any errors from the attempted command
            while ((s = stdError.readLine()) != null) {
                errorLines.add(s);
            }
            
            if ((lines.size() > 1) | (errorLines.size() > 0)) {
            	System.out.println("Problem getting date time tag:\n\t" + lines + "\n\t" + errorLines);
            	return("Error");
            }
        }
        catch (IOException e) {
            System.out.println("exception happened - here's what I know: ");
            e.printStackTrace();
        }

        return(lines.get(0));

	}

	public static void main(String[] args) {
		DateTakenTest test = new DateTakenTest();
		test.processImageDirectory(new File("/media/1-5_DAS/photos"));
	}

}
